package com.ow.dva.module.permission.service.impl;

import com.ow.dva.config.annotation.DvaCache5M;
import com.ow.dva.module.permission.entity.Permission;
import com.ow.dva.module.permission.entity.Role;
import com.ow.dva.module.permission.entity.RolePermission;
import com.ow.dva.module.permission.mapper.PermissionMapper;
import com.ow.dva.module.permission.service.PermissionService;
import com.ow.dva.module.base.service.impl.DvaServiceImpl;
import com.ow.dva.module.permission.service.RolePermissionService;
import org.springframework.stereotype.Service;
import com.ow.dva.module.base.entity.param.DvaPage;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * <p>
 * 权限表 服务实现类
 * </p>
 *
 * @author 高祥
 * @since 2020-01-09
 * @version V1.0
 */
@Service
public class PermissionServiceImpl extends DvaServiceImpl<PermissionMapper, Permission> implements PermissionService {

    @DvaCache5M
    @Override
    public DvaPage<Permission> page(DvaPage<Permission> page, Map<String, Object> param) {
        DvaPage<Permission> dvaPage = baseMapper.page(page,param);
        dvaPage.getRecords().forEach(permission -> {
            //获取父级信息
            permission.setParent(baseMapper.selectById(permission.getParentId()));
            //获取所有直属下级信息
            permission.setChildCount(baseMapper.selectByParentId(permission.getId()).size());
        });
        return dvaPage;
    }

    @Override
    public List<Permission> listAll() {

        return getPermissions(baseMapper.selectList(null));
    }

    @Override
    public List<Permission> selectByAccountId(String accountId) {

        return getPermissions(baseMapper.selectByAccountId(accountId));
    }

    @Override
    public List<Permission> selectAllWithRoleId(String roleId) {
        List<Permission> list = baseMapper.selectAllWithRoleId(roleId);
        list.forEach(permission -> {
            permission.setDataJsTree("{\"selected\":"+(permission.getRoleId()!=null?true:false) + ",\"icon\":\"" + permission.getIcon() + "\"}");
        });
        return getPermissions(list);
    }

    @Override
    public List<Permission> selectByRoleId(String roleId) {

        return baseMapper.selectByRoleId(roleId);
    }

    @Override
    public List<Permission> selectByParentId(String parentId) {

        return baseMapper.selectByParentId(parentId);
    }

    @Override
    public Boolean quickSave(String name, String url) {
        String id = saveManagerPermission(name,url);
        if(id != null){
            savePagePermission(id,name,url);
            saveAddPermission(id,name,url);
            saveEditPermission(id,name,url);
            saveDeletePermission(id,name,url);
            return true;
        }
        return false;
    }

    public String saveManagerPermission(String name,String url){
        if(isHaveName(name + "管理")) return null;
        Permission permission = new Permission();
        permission.setIcon("fa fa-user icon-state-info icon-lg");
        permission.setIntro("管理" + name + "模块的增删改查信息");
        permission.setName(name + "管理");
        permission.setParentId("0");
        permission.setShiro(url);
        permission.setUrl("");
        permission.setParam("");
        List<Permission> list = selectByParentId("0");
        permission.setSort(list.size()+1);
        permission.setType(0);

        save(permission);
        saveRoleToAdmin(permission.getId());
        return permission.getId();
    }

    public Boolean savePagePermission(String parentId,String name,String url){
        if(isHaveName(name + "列表")) return false;
        Permission permission = new Permission();
        permission.setIcon("fa fa-user icon-state-success");
        permission.setIntro("管理" + name + "模块列表信息");
        permission.setName(name + "列表");
        permission.setParentId(parentId);
        permission.setShiro(url + ":page");
        permission.setUrl("/" + url + "/page");
        permission.setParam("&current=1&size=10");
        permission.setSort(countSort(parentId));
        permission.setType(0);
        boolean success = save(permission);
        boolean role = saveRoleToAdmin(permission.getId());
        return success && role;
    }

    public Boolean saveAddPermission(String parentId,String name,String url){
        if(isHaveName(name + "添加")) return false;
        Permission permission = new Permission();
        permission.setIcon("fa  fa-plus icon-state-info");
        permission.setIntro("管理" + name + "模块添加权限");
        permission.setName(name + "添加");
        permission.setParentId(parentId);
        permission.setShiro(url + ":add");
        permission.setUrl("/" + url + "/add");
        permission.setSort(countSort(parentId));
        permission.setType(1);
        boolean success = save(permission);
        boolean role = saveRoleToAdmin(permission.getId());
        return success && role;
    }

    public Boolean saveEditPermission(String parentId,String name,String url){
        if(isHaveName(name + "编辑")) return false;
        Permission permission = new Permission();
        permission.setIcon("fa  fa-edit icon-state-warning");
        permission.setIntro("管理" + name + "模块编辑/查看权限");
        permission.setName(name + "编辑");
        permission.setParentId(parentId);
        permission.setShiro(url + ":edit");
        permission.setUrl("/" + url + "/edit");
        permission.setSort(countSort(parentId));
        permission.setType(1);
        boolean success = save(permission);
        boolean role = saveRoleToAdmin(permission.getId());
        return success && role;
    }

    public Boolean saveDeletePermission(String parentId,String name,String url){
        if(isHaveName(name + "删除")) return false;
        Permission permission = new Permission();
        permission.setIcon("fa  fa-trash-o icon-state-danger");
        permission.setIntro("管理" + name + "模块删除权限");
        permission.setName(name + "删除");
        permission.setParentId(parentId);
        permission.setShiro(url + ":delete");
        permission.setUrl("/" + url + "/delete");
        permission.setSort(countSort(parentId));
        permission.setType(1);
        boolean success = save(permission);
        boolean role = saveRoleToAdmin(permission.getId());
        return success && role;
    }

    /**
     * 判断是否存在同名权限，存在则不添加
     * @param name 权限名称
     * @return 存在返回 true
     */
    public Boolean isHaveName(String name){
        Map<String,Object> param = new HashMap<>();
        param.put("name",name);
        List<Permission> list = baseMapper.selectByMap(param);
        return list.size() > 0;
    }

    /**
     * 权限给超级管理员授权
     * @param permissionId 权限ID
     */
    public Boolean saveRoleToAdmin(String permissionId){
        RolePermission rolePermission = new RolePermission();
        rolePermission.setRoleId("888888");
        rolePermission.setPermissionId(permissionId);
        return rolePermissionService.save(rolePermission);
    }

    /**
     * 获取当前同级中的排序
     * @param parentId 上级
     */
    public Integer countSort(String parentId){
        List<Permission> list = selectByParentId(parentId);
        return list.size() + 1;
    }

    /**
     * 整理权限格式，分上下级，最多支持三级。
     * 创建时间：2020-02-12 高祥
     * 修改时间：2020-02-12 高祥 加注释
     * 修改时间：
     * @param p 无序无格式的权限列表
     * @return 有格式的权限列表
     */
    private List<Permission> getPermissions(List<Permission> p) {
        List<Permission> menu = searchListByParentId(p,"0");
        for(Permission pp : menu){
            pp.setPermissions(searchListByParentId(p,pp.getId()));
            for(Permission ppp : pp.getPermissions()){
                ppp.setPermissions(searchListByParentId(p,ppp.getId()));
            }
        }
        return menu;
    }


    /**
     * 在某集合 list 中根据 parentId 筛选出所有下级。
     * 创建时间：2020-02-12 高祥
     * 修改时间：2020-02-12 高祥 加注释
     * 修改时间：
     * @param list  无格式集合
     * @param parentId 上级ID
     * @return 有格式集合
     */
    private List<Permission> searchListByParentId(List<Permission> list,String parentId){
        List<Permission> temp = new ArrayList<>();
        for(Permission p : list){
            if(p.getParentId().equals(parentId)){
                temp.add(p);
            }
        }
        return temp;
    }


    @Resource
    RolePermissionService rolePermissionService;
}
